package com.resolution.dietaryassessment.view.mydietary.fragment;

import android.annotation.SuppressLint;
import android.os.Bundle;
import android.os.Looper;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.LinearLayout;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Lifecycle;
import androidx.recyclerview.widget.GridLayoutManager;
import androidx.recyclerview.widget.RecyclerView;

import com.example.rxbus.RxBus;
import com.example.rxbus.bean.BreakFastEvent;
import com.example.rxbus.bean.DinnerEvent;
import com.example.rxbus.bean.LunchEvent;
import com.example.rxbus.bean.StatusEvent;
import com.google.android.material.tabs.TabLayout;
import com.resolution.dietaryassessment.R;
import com.resolution.dietaryassessment.databeans.CommonConfig;
import com.resolution.dietaryassessment.databeans.EnergyRadioBean;
import com.resolution.dietaryassessment.databeans.MealRatioBean;
import com.resolution.dietaryassessment.databeans.UserRealData;
import com.resolution.dietaryassessment.view.mydietary.adapter.MyRecyclerViewAdapter;
import com.resolution.dietaryassessment.view.mydietary.adapter.RecyclerSimpleAdapter;
import com.resolution.dietaryassessment.view.mydietary.bean.FoodInfoBean;
import com.resolution.dietaryassessment.view.mydietary.bean.FoodTotalCalories;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;

import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;
import butterknife.Unbinder;
import es.dmoral.toasty.Toasty;

import static android.content.ContentValues.TAG;
import static com.resolution.dietaryassessment.view.mydietary.constant.ConstantBean.*;
import static com.resolution.dietaryassessment.view.mydietary.helper.initFoodHelper.*;

/**
 * @author By Resolusion
 * @Title:
 * @Date: 2020/4/13
 * @Time: 15:55
 * @email Res01ution@foxmail.com
 */
public class ChoiceFoodFrag extends Fragment implements InspectObj, TabLayout.OnTabSelectedListener {
    @BindView(R.id.tablayout)
    TabLayout tablayout;
    @BindView(R.id.tab_recycler)
    RecyclerView tabRecycler;
    @BindView(R.id.zaochan_recycler)
    RecyclerView zaochanRecycler;
    @BindView(R.id.breakfast_lay)
    LinearLayout breakfastLay;
    @BindView(R.id.lunch_lay)
    LinearLayout lunchLay;
    @BindView(R.id.dinner_lay)
    LinearLayout dinnerLay;
    @BindView(R.id.lunch_recycler)
    RecyclerView lunchRecycler;
    @BindView(R.id.dinner_recycler)
    RecyclerView dinnerRecycler;

    private Unbinder unbinder;

    private List<FoodTotalCalories> breakfast_list = new ArrayList<>();
    private List<FoodTotalCalories> lunch_list = new ArrayList<>();
    private List<FoodTotalCalories> dinner_list = new ArrayList<>();

    //判断食物数量是否超出范围
    private int Flag = 0;
    //餐次标志
    private int status = -1;
    private UserRealData userRealData = new UserRealData(0, 0, 0, 0);

    private int break_heat = 0;
    private int lunch_heat = 0;
    private int dinner_heat = 0;

    private float carbon_zb;
    private float protein_zb;
    private float fat_zb;

    private List<Float> carbon_list = new ArrayList<>();
    private List<Float> protein_list = new ArrayList<>();
    private List<Float> fat_list = new ArrayList<>();

    private List<Float> proteinSourceList = new ArrayList<>();

    private float sumCarbon = 0, sumProtein = 0, sumFat = 0;
    private int sumHeat;

    private RecyclerSimpleAdapter breakAdapter = new RecyclerSimpleAdapter(breakfast_list);
    private RecyclerSimpleAdapter lunchAdapter = new RecyclerSimpleAdapter(lunch_list);
    private RecyclerSimpleAdapter dinnerAdapter = new RecyclerSimpleAdapter(dinner_list);

    private MyRecyclerViewAdapter tableAdapter;
    private List<List<FoodInfoBean>> foodCardList = new ArrayList<>();

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_choice_food, container, false);
        unbinder = ButterKnife.bind(this, view);
        initView();
        return view;
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState);
        initTable();
    }

    @OnClick({R.id.breakfast_lay, R.id.lunch_lay, R.id.dinner_lay})
    void onViewClicked(View view) {
        switch (view.getId()) {
            case R.id.breakfast_lay:
                status = BREAKFAST_STATUS;
                JudgmentBackground();
                break;
            case R.id.lunch_lay:
                status = LUNCH_STATUS;
                JudgmentBackground();
                break;
            case R.id.dinner_lay:
                status = DINNER_STATUS;
                JudgmentBackground();
                break;
        }
    }

    @Override
    public boolean inspectObj() {
        return breakfast_list.size() != 0 || lunch_list.size() != 0 || dinner_list.size() != 0;
    }

    @Override
    public void onPause() {
        super.onPause();
        break_heat = calculateHeat(breakAdapter.getFoodTotalCaloriesList());
        lunch_heat = calculateHeat(lunchAdapter.getFoodTotalCaloriesList());
        dinner_heat = calculateHeat(dinnerAdapter.getFoodTotalCaloriesList());
        calculateSumHeat();
        CalculationElementProportion();
    }

    @Override
    public void onDestroyView() {
        super.onDestroyView();
        unbinder.unbind();
    }

    @Override
    public void onTabSelected(TabLayout.Tab tab) {
        tableAdapter.setData(foodCardList.get(tab.getPosition()));
    }

    @Override
    public void onTabUnselected(TabLayout.Tab tab) {

    }

    @Override
    public void onTabReselected(TabLayout.Tab tab) {

    }

    @SuppressLint("CheckResult")
    private void initView() {
        initRecycler();

        RxBus.getInstance().toObservable(getActivity(), BreakFastEvent.class, Lifecycle.Event.ON_ANY)
                .subscribe(breakFastEvent -> {
                    FoodTotalCalories obj = (FoodTotalCalories) breakFastEvent.getObj();
                    /*
                    数据定义
                     */
                    breakfast_list.add(obj);
                    breakAdapter.setFoodTotalCaloriesList(breakfast_list);
                    /*
                    数据计算
                     */
                    judgementData(breakAdapter.getFoodTotalCaloriesList());
                    getFoodElement(breakAdapter.getFoodTotalCaloriesList());
                });

        RxBus.getInstance().toObservable(getActivity(), LunchEvent.class, Lifecycle.Event.ON_ANY)
                .subscribe(lunchEvent -> {
                    FoodTotalCalories obj = (FoodTotalCalories) lunchEvent.getObj();
                    lunch_list.add(obj);
                    lunchAdapter.setFoodTotalCaloriesList(lunch_list);
                    judgementData(lunchAdapter.getFoodTotalCaloriesList());
                    getFoodElement(lunchAdapter.getFoodTotalCaloriesList());
                });

        RxBus.getInstance().toObservable(getActivity(), DinnerEvent.class, Lifecycle.Event.ON_ANY)
                .subscribe(dinnerEvent -> {
                    FoodTotalCalories obj = (FoodTotalCalories) dinnerEvent.getObj();
                    dinner_list.add(obj);
                    dinnerAdapter.setFoodTotalCaloriesList(dinner_list);
                    judgementData(dinnerAdapter.getFoodTotalCaloriesList());
                    getFoodElement(dinnerAdapter.getFoodTotalCaloriesList());
                });
    }

    /**
     * 初始化tableLayout
     */
    private void initTable() {
        String[] tableTitle = getResources().getStringArray(R.array.title);
        for (int i = 0; i < tableTitle.length; i++) {
            tablayout.addTab(tablayout.newTab());
            tablayout.getTabAt(i).setText(tableTitle[i]);
        }
        tablayout.addOnTabSelectedListener(this);
        tableAdapter = new MyRecyclerViewAdapter();
        tableAdapter.setData(foodCardList.get(0));
        tabRecycler.setAdapter(tableAdapter);
        tabRecycler.setLayoutManager(new GridLayoutManager(getActivity(), 3,
                RecyclerView.HORIZONTAL, false));
    }

    /**
     * 初始化RecyclerView
     */
    private void initRecycler() {
        setRecycler(zaochanRecycler, breakAdapter);
        setRecycler(lunchRecycler, lunchAdapter);
        setRecycler(dinnerRecycler, dinnerAdapter);
        Collections.addAll(foodCardList, initStapleFood(), initVegetable(), initFruit(),
                initDiredFruit(), initMeat(), initOil(), initDairyProduct(), initSnack(), initDrinks());
    }

    private void setRecycler(RecyclerView recycler, RecyclerSimpleAdapter adapter) {
        recycler.setHasFixedSize(true);
        recycler.setLayoutManager(new GridLayoutManager(getContext(), 5));
        recycler.setAdapter(adapter);
    }

    /**
     * 更新数据
     */
    private void upData(List<String> idList) {
        if (status == BREAKFAST_STATUS) {
           setAdapterDelClick(idList,breakAdapter);
        } else if (status == LUNCH_STATUS) {
            setAdapterDelClick(idList,lunchAdapter);
        } else if (status == DINNER_STATUS) {
            setAdapterDelClick(idList,dinnerAdapter);
        }
    }

    /**
     * 根据adapter更新数据
     */
    private void setAdapterDelClick(List<String> idList,RecyclerSimpleAdapter adapter){
        adapter.setDelClick(new DelClick() {
            @Override
            public void delClick(int position) {
                idList.remove(position);
            }

            @Override
            public void elementListener(int position) {
                carbon_list.remove(position);
                protein_list.remove(position);
                fat_list.remove(position);
            }

            @Override
            public void delHQProtein(int position) {
                for (int i = proteinSourceList.size() - 1; i >= 0; i--){
                    if (protein_list.get(position).equals(proteinSourceList.get(i))){
                        proteinSourceList.remove(i);
                    }
                }
            }
        });
        adapter.notifyDataSetChanged();
    }

    /**
     * 选中餐次设置背景
     */
    private void JudgmentBackground() {
        RxBus.getInstance().post(new StatusEvent<Integer>(status));
        switch (status) {
            case BREAKFAST_STATUS:
                breakfastLay.setBackground(getResources().getDrawable(R.drawable.meal_card_check_bg));
                lunchLay.setBackground(null);
                dinnerLay.setBackground(null);
                break;
            case LUNCH_STATUS:
                lunchLay.setBackground(getResources().getDrawable(R.drawable.meal_card_check_bg));
                breakfastLay.setBackground(null);
                dinnerLay.setBackground(null);
                break;
            case DINNER_STATUS:
                dinnerLay.setBackground(getResources().getDrawable(R.drawable.meal_card_check_bg));
                lunchLay.setBackground(null);
                breakfastLay.setBackground(null);
                break;
        }
    }

    /**
     * 为选中餐次添加数据，并判断
     */
    private void judgementData(List<FoodTotalCalories> list) {
        List<String> idList = new ArrayList<>();
        for (FoodTotalCalories foodTotalCalories : list) {
            idList.add(foodTotalCalories.getName());
        }
        HashSet<String> set = new HashSet<>(idList);
        boolean result = idList.size() == set.size();
        if (result) {
            if (list.size() >= 1 && list.size() <= 10) {
                upData(idList);
            } else if (list.size() > 10) {
                Toasty.warning(getContext(), "餐桌已经放不下了！请注意控制热量摄入").show();
            }
        } else {
            Toasty.warning(getContext(), "您已经添加过相同的食物了").show();
            list.remove(list.size() - 1);
            idList.remove(idList.size() - 1);
            Flag = 1;
        }
    }

    /**
     * 计算各餐次热量
     */
    private int calculateHeat(List<FoodTotalCalories> list) {
        int heat = 0;
        for (int i = 0; i < list.size(); i++) {
            heat = list.get(i).getCalories() + heat;
        }
        Log.d(TAG, "calculateHeat: " + heat);
        return heat;
    }

    /**
     * 计算总热量以及各餐次供能占比
     */
    private void calculateSumHeat() {
        //总热量
        sumHeat = break_heat + lunch_heat + dinner_heat;
        //餐次比
        float zaocanRatio = ((float) break_heat / (float) sumHeat) * 100;
        float lunchRatio = ((float) lunch_heat / (float) sumHeat) * 100;
        float dinnerRatio = ((float) dinner_heat / (float) sumHeat) * 100;
        Log.d(TAG, "calculateSumHeat: " + sumHeat);

        userRealData.setUserHeat(sumHeat);

        CommonConfig.getInstance().setMealRatioBean(new MealRatioBean((int) zaocanRatio,
                (int) lunchRatio, (int) dinnerRatio));
    }

    /**
     * 获取三大营养元素各项供能
     */
    @SuppressLint("CheckResult")
    private void getFoodElement(List<FoodTotalCalories> breakfast_list) {
        int hit = 0;
        for (int i = 0; i < breakfast_list.size(); i++) {
            hit = breakfast_list.get(i).getCalories();
        }
        Log.d(TAG, "getFoodElement: " + breakfast_list.size());
        switch (tablayout.getSelectedTabPosition()) {
            case STAPLE_FOOD_STATUS:
                carbon_zb = (float) (hit * 0.85);
                protein_zb = (float) (hit * 0.1);
                fat_zb = (float) (hit * 0.05);
                break;
            case VEGETABLE_STATUS:
                carbon_zb = (float) (hit * 0.65);
                protein_zb = (float) (hit * 0.3);
                fat_zb = (float) (hit * 0.05);
                break;
            case FRUIT_STATUS:
                carbon_zb = (float) (hit * 0.94);
                protein_zb = (float) (hit * 0.03);
                fat_zb = (float) (hit * 0.03);
                break;
            case DRY_FRUIT_STATUS:
                carbon_zb = (float) (hit * 0.11);
                protein_zb = (float) (hit * 0.09);
                fat_zb = (float) (hit * 0.80);
                break;
            case MEAT_STATUS:
                carbon_zb = (float) (hit * 0.03);
                protein_zb = (float) (hit * 0.57);
                fat_zb = (float) (hit * 0.40);
                proteinSourceList.add(protein_zb);
                break;
            case OIL_STATUS:
                carbon_zb = 0;
                protein_zb = 0;
                fat_zb = (float) hit;
                break;
            case DAIRY_STATUS:
                carbon_zb = (float) (hit * 0.25);
                protein_zb = (float) (hit * 0.22);
                fat_zb = (float) (hit * 0.53);
                proteinSourceList.add(protein_zb);
                break;
            case SNACK_STATUS:
                carbon_zb = (float) (hit * 0.75);
                protein_zb = (float) (hit * 0.1);
                fat_zb = (float) (hit * 0.15);
                break;
            case DRINK_STATUS:
                carbon_zb = (float) (hit * 0.96);
                protein_zb = (float) (hit * 0.04);
                fat_zb = 0;
                break;
        }
        if (Flag == 0) {
            carbon_list.add(carbon_zb);
            protein_list.add(protein_zb);
            fat_list.add(fat_zb);
        } else {
            Flag = 0;
        }
    }

    /**
     * 计算各元素重量
     */
    private void CalculationElementProportion() {
        Log.d(TAG, "CalculationElementProportion: " + protein_list);
        for (int i = 0; i < carbon_list.size(); i++) {
            sumCarbon = carbon_list.get(i) + sumCarbon;
        }
        for (int i = 0; i < protein_list.size(); i++) {
            sumProtein = protein_list.get(i) + sumProtein;
        }
        for (int i = 0; i < fat_list.size(); i++) {
            sumFat = fat_list.get(i) + sumFat;
        }

        System.out.println("...sum:..." + sumCarbon + "..." + sumProtein + "..." + sumFat);

        //碳水重量
        int carbon_w = (int) (sumCarbon / 4);
        //蛋白质重量
        int protein_w = (int) (sumProtein / 4);
        //脂肪重量
        int fat_w = (int) (sumFat / 9);

        int cb_radio = (int) ((sumCarbon / sumHeat) * 100);
        int pt_radio = (int) ((sumProtein / sumHeat) * 100);
        int fat_radio = (int) ((sumFat / sumHeat) * 100);

        System.out.println(cb_radio + "<<>>" + pt_radio);

        userRealData.setUserCBHR(carbon_w);
        userRealData.setUserProtein(protein_w);
        userRealData.setUserFat(fat_w);

        CommonConfig.getInstance().setUserRealData(userRealData);
        CommonConfig.getInstance().setEnergyRadioBean(new EnergyRadioBean(pt_radio, fat_radio, cb_radio));

        calculationProteinSource();

        sumCarbon = 0;
        sumProtein = 0;
        sumFat = 0;
    }

    /**
     * 计算优质蛋白质比例
     */
    private void calculationProteinSource() {
        float sumHighProtein = 0;
        for (int i = 0; i < proteinSourceList.size(); i++) {
            sumHighProtein = proteinSourceList.get(i) + sumHighProtein;
        }
        int HighProtein = (int) ((sumHighProtein / sumProtein) * 100);
        Log.d(TAG, "calculationProteinSource: " + proteinSourceList);
        CommonConfig.getInstance().setProteinSource(HighProtein);
    }
}
